use std::{f64::consts::E, sync::{
    atomic::{AtomicBool, Ordering},
    Arc, Mutex,
}};
use std::thread;

use super::super::utils::common;
use rust_decimal::prelude::*;
use rust_decimal::Decimal;
use serde::Deserialize;
use serde_json::{from_str, Value};
use sysinfo::{Components, CpuRefreshKind, Disks, Networks, RefreshKind, System};
use tauri::State;
use tauri::{Manager, Window, WindowEvent};

#[derive(Clone, serde::Serialize)]
struct Payload {
    message: String,
    timestamp: i64,
}

pub struct AppSate {
    pub should_stop: Arc<AtomicBool>,
}

#[tauri::command]
pub fn init_process(window: Window, state: State<'_, AppSate>) {
    let should_stop = state.should_stop.clone();
    thread::spawn(move || loop {
        if should_stop.load(Ordering::Relaxed) {
            println!("Task stoped!");
            should_stop.store(false, Ordering::Relaxed);
        }
        let timestamp = common::get_current_time();
        println!("{}", timestamp);
        window
            .emit(
                "my-event",
                Payload {
                    message: "Hello from Rust!".to_string(),
                    timestamp: timestamp,
                },
            )
            .unwrap();
        common::sleep(6);
    });
}

#[derive(Clone, serde::Serialize)]
struct SystemInfo {
    os_name: String,
    os_version: String,
    host_name: String,
    kernel_version: String,
    cpu_name: String,
    cpu_cores: i32,
    cpu_thread_count: i32,
}

#[derive(Clone, serde::Serialize)]
struct SystemCpu {
    cpu_usage: f32,
    used_memory: f32,
    free_memory: f32,
    used_swap: f32,
    free_swap: f32,
}

#[derive(Deserialize)]
struct StopEvent {
    is_stop: bool,
}

#[tauri::command]
pub fn collet_cpu(window: Window) {
    let mut sys: System = System::new_all();
    // GB
    let size = 1024.0 * 1024.0 * 1024.0;

    sys.refresh_memory();
    // bytes
    let total_memory = sys.total_memory();
    let total_swap = sys.total_swap();

    println!("total memory: {} bytes", total_memory);
    println!("total swap  : {} bytes", total_swap);

    let should_stop = Arc::new(AtomicBool::new(false));
    let should_stop1 = should_stop.clone();
    let window_ = window.clone();

    thread::spawn(move || {
        let id = thread::current().id();
        loop {
            if should_stop.load(Ordering::Relaxed) {
                println!("thread{:?} Task stoped!", id);
                println!("{}", "退出线程");
                break;
            }
            println!("thread{:?}  sys refresh", id);
            sys.refresh_cpu_usage();
            sys.refresh_memory();

            let used_memory = sys.used_memory();
            let free_memory = total_memory - used_memory;

            let used_swap = sys.used_swap();
            let free_swap = total_swap - used_swap;

            let float_used_memory = Decimal::from_f32(used_memory as f32 / size)
                .unwrap()
                .round_dp(2)
                .to_f32()
                .unwrap();
            let float_free_memory = Decimal::from_f32(free_memory as f32 / size)
                .unwrap()
                .round_dp(2)
                .to_f32()
                .unwrap();

            let float_used_swap = Decimal::from_f32(used_swap as f32 / size)
                .unwrap()
                .round_dp(2)
                .to_f32()
                .unwrap();
            let float_free_swap = Decimal::from_f32(free_swap as f32 / size)
                .unwrap()
                .round_dp(2)
                .to_f32()
                .unwrap();

            // sys.refresh_cpu();

            // for cpu in sys.cpus() {
            //     println!("{} {}% {} {} {}", cpu.name(), cpu.cpu_usage(), cpu.frequency(), cpu.brand(), cpu.vendor_id());
            // }

            window
                .emit(
                    "collet_cpu",
                    SystemCpu {
                        cpu_usage: sys.global_cpu_info().cpu_usage(),
                        used_memory: float_used_memory,
                        free_memory: float_free_memory,
                        used_swap: float_used_swap,
                        free_swap: float_free_swap,
                    },
                )
                .unwrap();
           

            common::sleep(1);
        }
    });

    println!("监听 StopEvent");
   

    let handler = window_.once("StopEvent", move |event: tauri::Event| {
        println!("StopEvent {}", event.id());
        let payload_str = event.payload().unwrap().to_string();
        println!("{payload_str}");
        let payload: Result<StopEvent, serde_json::Error> = from_str(&payload_str);

        match payload {
            Ok(p) => {
                // *stop_event = p.is_stop;
                print!("StopEvent {}", p.is_stop);
                should_stop1.store(p.is_stop, Ordering::Relaxed);
            }
            Err(err) => {
                println!("Error decoding payload: {}", err);
            }
        }
        // window_.unlisten(event.clone().id());
    });
    //window_.unlisten(handler);
}
